package com.lmx.persistence.service;

import java.util.Date;
import java.util.List;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.joda.time.DateTime;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.google.common.collect.Lists;
import com.lmx.common.constants.CommonConstants;
import com.lmx.common.util.CommonUtil;
import com.lmx.persistence.service.common.BaseCrudServiceImpl;
import com.lmx.repoDomain.tmodel.Employee;
import com.lmx.repoDomain.tmodel.PersonLocation;
import com.lmx.repoDomain.tmodel.PersonLocationIoReport;
import com.lmx.repoDomain.tmodel.Tenant;

/**
 * 员工出入房间统计
 *
 * @author ytche
 * @date 2017年6月30日
 *
 */
@Service
public class PersonLocationIOReportServiceImpl extends
		BaseCrudServiceImpl<PersonLocationIoReport> implements
		PersonLocationIOReportService {
	private Log logger = LogFactory.getLog(this.getClass());
	@Autowired
	private PersonLocationService locationService;
	@Autowired
	private TenantService<Tenant> tenantService;
	@Autowired
	private EmployeeService<Employee> employeeService;

	@Override
	public void sysIOReportData(Long generateTime) {
		generateTime = generateTime == null ? new Date().getTime()
				: generateTime;
		this.cleanOldData(generateTime);
		List<Tenant> tenants = this.tenantService.findActiveTenant();
		if (tenants == null || tenants.size() < 1) {
			return;
		}
		for (Tenant tenant : tenants) {
			sysTenantData(tenant, generateTime, null, null);
		}
	}

	@Override
	public void sysIOReportData(Long startTime, Long endTime) {
		List<Tenant> tenants = this.tenantService.findActiveTenant();
		if (tenants == null || tenants.size() < 1) {
			return;
		}
		for (Tenant tenant : tenants) {
			sysTenantData(tenant, null, startTime, endTime);
		}

	}

	/**
	 * 同步租户的员工出入房间数据
	 *
	 * @author ytche
	 * @param tenant
	 * @param generatTime
	 * @param startTime
	 * @param endTime
	 * @date 2017年6月30日 下午4:31:37
	 */
	private void sysTenantData(Tenant tenant, Long generatTime, Long startTime,
			Long endTime) {
		logger.debug("同步租户数据,租户ID为---" + tenant.getId());
		List<Employee> employees = this.employeeService.findByTenant(tenant
				.getId());
		if (employees == null || employees.size() < 1) {
			return;
		}
		for (Employee employee : employees) {
			logger.debug("同步员工--" + employee.getName() + "数据,员工ID为---"
					+ employee.getId());
			List<PersonLocation> personsList = Lists.newArrayList();
			if (generatTime != null && startTime == null && endTime == null) {
				personsList = locationService.findRowDataByEmployee(
						employee.getId(), generatTime);
			}
			if (generatTime == null && startTime != null && endTime != null) {
				personsList = locationService.findRowDataByEmployee(
						employee.getId(), startTime, endTime);
			}
			if (personsList == null || personsList.size() < 1) {
				logger.debug(employee.getName() + "该时间段内共有 没有位置记录");
				continue;
			}
			logger.debug(employee.getName() + "该时间段内共有 " + personsList.size()
					+ "条记录");
			// 暂存当前房间信息
			PersonLocation personLocation = personsList.get(0);
			for (int i = 1; i < personsList.size(); i++) {
				PersonLocation rowData = personsList.get(i);
				// 房间改变和最后一条数据时生成进出房间的数据
				if (i < personsList.size() - 1
						&& rowData.getRoom().getId()
								.equals(personLocation.getRoom().getId())) {
					continue;
				}
				PersonLocationIoReport report = new PersonLocationIoReport();
				Integer generatInt = generatTime != null ? (int) (generatTime / 1000)
						: (int) (startTime / 1000);
				report.setGeneratorTime(generatInt);
				report.setEmployee(employee);
				report.setTenant(employee.getTenant());
				report.setRoom(personLocation.getRoom());
				report.setInTime(personLocation.getCreateDateTime());
				// 取房间改变时的上一条数据的创建时间为离开房间时间
				report.setOutTime(personsList.get(i - 1).getCreateDateTime());
				report.setDelStatus(CommonConstants.DEL_STATUS_NO_0);
				report = save(report);
				
				// 修改之前的离开记录
					// 获取当天上一次的房间出入记录
				List<PersonLocationIoReport> reports = findOfDay(employee.getId(), generatTime);
				if (reports.size() > 1) {
					PersonLocationIoReport lastReport = reports.get(reports.size() - 2);
					lastReport.setOutTime(report.getInTime());	// 设置当前进房间时间为上条出房间时间
					lastReport.setStayMinites(Double.valueOf((lastReport.getOutTime() - lastReport.getInTime()) / 60).intValue());
					update(lastReport);
				}
				
				logger.debug("生成出入房间数据,id为" + report.getId());
				// 房间更新为当前房间
				personLocation = personsList.get(i);
			}
		}

	}

	/**
	 * 重复同步同一天数据的时候清除旧数据
	 *
	 * @author ytche
	 * @param generateTime
	 * @date 2017年7月3日 下午5:17:06
	 */
	private void cleanOldData(Long generateTime) {
		Integer start = CommonUtil.getDayBegin(new Date(generateTime));
		Integer end = CommonUtil.getDayBegin(new DateTime(generateTime)
				.plusDays(1).toDate());
		String queryStr = "delete from PersonLocationIoReport where generatorTime>= :start and generatorTime < :end ";
		super.em.createQuery(queryStr).setParameter("start", start)
				.setParameter("end", end).executeUpdate();
	}

	@Override
	public List<PersonLocationIoReport> findOfDay(Long employeeId, Long dayTime) {
		Integer startTime = CommonUtil.getDayBegin(new Date(dayTime));
		Integer endTime = CommonUtil.getDayBegin(new DateTime(dayTime)
				.plusDays(1).toDate());
		String queryStr = "from PersonLocationIoReport as l where l.delStatus = 0 "
				+ " and l.employee.id =:employeeId and l.generatorTime >= :startTime "
				+ " and l.generatorTime < :endTime";
		return super.em.createQuery(queryStr)
				.setParameter("employeeId", employeeId)
				.setParameter("startTime", startTime)
				.setParameter("endTime", endTime).getResultList();
	}
}
